/**

 * SPA
 * Classification: Inherited
 * Clearance: Internal Restricted
 * ----------------------------------------
 * DSP
 * Classification: External Restricted
 * Clearance: External Restricted
 * 
 * @throws OjiException
 *  Test User : Stuart Downs (ID - uA446)
 * 
 */

package admin;

import java.io.BufferedReader;
import java.io.DataInputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Iterator;
import java.util.List;
import java.util.Set;

import test.LocalProperties;


import com.objective.oji.OjiAlias;
import com.objective.oji.OjiClassifiedObjectException;
import com.objective.oji.OjiException;
import com.objective.oji.OjiFolder;
import com.objective.oji.OjiGroup;
import com.objective.oji.OjiObject;
import com.objective.oji.OjiSearch;
import com.objective.oji.OjiTypeDefn;
import com.objective.oji.OjiUser;

public class Obj_Users extends LocalObjSession {

    final String INACTIVE = "INACTIVE";
    final String ACTIVE = "ACTIVE";
    final String userGroupActive_ID = "gA2";
    final String userGroupInactive_ID = "gA3";
    final String Security_Clearance_DSP = "5";

    public Obj_Users(LocalProperties AppProfile, SERVER_TYPE Selected_SERVER_PROFILE, LOGINMETHOD Login_Method_TYPE) {
	super(AppProfile, Selected_SERVER_PROFILE, Login_Method_TYPE);
    }

    public boolean getUserDetails() {

	// OjiUser newUser = apiSession.initUser();
	// String userID = "uA446";
	String userID = "uA993";
	//String folderID = "fA5179";

	String ActiveUserGroupID = "gA2";

	OjiUser existUser = (OjiUser) apiSession.getObject(userID);
	//OjiFolder existUserFolder = (OjiFolder) apiSession.getObject(userID);
	try {
	    System.out.println("Obj ID:                 " + existUser.getObjId());
	    System.out.println("Login ID:               " + existUser.getLoginId());
	    System.out.println("Classification:         " + existUser.getClassification());
	    System.out.println("Clearance:              " + existUser.getSecurityClearance());
	    System.out.println("Home Folder:            " + existUser.getHomeFolder().getName());
	    System.out.println("Parent Name:            " + existUser.getParent().getName());
	    OjiGroup parentGroup = (OjiGroup) existUser.getParent();
	    System.out.println("Parent Name:            " + parentGroup.getName());
	    OjiGroup activeUserGroup = (OjiGroup) apiSession.getObject(ActiveUserGroupID);
	    System.out.println(activeUserGroup.getName());
	    System.out.println(existUser.getAssistant());
	    System.out.println(existUser.getEmailAddress());

	} catch (OjiClassifiedObjectException e) {
	    e.printStackTrace();
	}

	return false;

	// OjiGroup activeUserGroup = (OjiGroup) apiSession.getObject(objID);

    }

    public void createTestUsers(int number) {

	final String businessDomain = "SPA";
	final String userNameBase = "ObjUpgTest";
	final Integer numberOfUsers = 30;
	final Integer delaysec = 30;

	for (Integer i = 1; i <= numberOfUsers; i++) {
	    String name = userNameBase + i.toString();
	    String email = name;
	    String lanID = name;
	    String password = name;

	    try {
		if (createUser(businessDomain, name, email, lanID, password)) {
		    System.out.println("created with success: " + name);
		} else {
		    System.err.println("failed to create a new user: " + name);
		}
	    } catch (OjiException e) {
		e.printStackTrace();
	    }
	    AdminTools.timeDelay(delaysec);
	}
    }

    public boolean removeUserFromGroups(String UserObjID) throws OjiException {

	/*
	 * UserObjID - USER OBJECT ID 1. CHECK IF THERE ARE MOER THAN A USER WHO HAS SAME NAME ==>
	 * STOP 2. SEARCH ALIAS
	 * BASED ON THE USER NAME 3. DELETE ALIAS ONLY
	 */

	final int Max_return_count = 100;

	final OjiUser user = (OjiUser) apiSession.getObject(UserObjID);
	Integer SAME_NAME_USER_COUNT = 0;

	// CHECK IF THERE ARE TWO USERS WITH SAME NAME
	try {
	    Search_Builder Search_USERS = new Search_Builder(apiSession, Max_return_count);
	    Search_USERS.set_Search_type("user");
	    Search_USERS.addCriteria("name", "is exactly", user.getName());
	    Collection<OjiObject> searchReturns;
	    searchReturns = Search_USERS.execute();
	    SAME_NAME_USER_COUNT = searchReturns.size();
	} catch (OjiException e) {
	    e.printStackTrace();
	}

	if (SAME_NAME_USER_COUNT > 1) {
	    System.out.println("WARNING: More than 1 user with same name - " + user.getName());
	    return true;
	} else {
	    try {
		Search_Builder Search_Aliases = new Search_Builder(apiSession, Max_return_count);
		Search_Aliases.set_Search_type("alias");
		Search_Aliases.addCriteria("name", "is exactly", user.getName() + " alias");
		Collection<OjiObject> searchReturns_Alias;
		searchReturns_Alias = Search_Aliases.execute();
		Iterator<OjiObject> i = searchReturns_Alias.iterator();

		while (i.hasNext()) {
		    OjiAlias searchResult = (OjiAlias) i.next();
		    String alias_name = searchResult.getLabelForView();
		    System.out.print("Alias : " + alias_name);
		    System.out.println("    Name: " + alias_name.replace(" alias", ""));
		    OjiObject group = (OjiObject) searchResult.getParent();
		    System.out.println("Group Name: " + group.getName());
		    searchResult.delete(); // NO UPDATE() REQUIRED
		}
	    } catch (OjiException e) {
		e.printStackTrace();
	    }
	}
	/*
	 * HANDLING GROUPS
	 */
	/*
	 * Set<com.objective.client.ObjGroup > listGroups =user.getBelongingGroups();
	 * Iterator<com.objective.client.ObjGroup > i = listGroups.iterator(); while (i.hasNext()) {
	 * com.objective.client.ObjGroup group = (com.objective.client.ObjGroup ) i.next();
	 * System.out.println(group.getName()); }
	 */
	return true;

    }

    public void changeUserGroup(String objID) throws OjiException {

    }

    private void SAR_setUserInactive(String objID) throws OjiException {

	// 1. turn Inactivated flag on
	// 2. move the user to the inactivated Group

	OjiUser user = (OjiUser) apiSession.getObject(objID);
	user.setParent((OjiGroup) apiSession.getObject(userGroupInactive_ID));
	user.inactivate();
	user.update();
	System.out.println("user INACTIVATED");

    }

    private boolean SAR_move_inactivated_users_X_folder() {

	/*
	 * SEARCH ---------------------------
	 * 1.SEARCH ALL INACTIVATED USERS
	 * 2.CHECK THE USER LAN ID SHOWN IN THE X FOLDER
	 * 3.MOVE TO XXX FOLDER
	 */

	/*
	 * clearance = SPA / DSP activeStatus = ACTIVE / INACTIVE
	 */
	final int Max_return_count = 3000;
	final String BASE_SRC_FP = "x:\\";
	final String BASE_DEST_FP = "x:\\ZZZ Deleted Accounts\\";

	try {
	    Search_Builder userSearch = new Search_Builder(apiSession, Max_return_count);
	    userSearch.set_Search_type("user");
	    userSearch.addCriteria("date inactivated", "is not blank", "");

	    Collection<OjiObject> results = userSearch.execute();
	    Iterator<OjiObject> i = results.iterator();

	    while (i.hasNext()) {
		OjiUser user = (OjiUser) i.next();
		System.out.print(user.getName() + ", " + user.getLoginId() + "   ");

		String srcFP = BASE_SRC_FP + user.getLoginId();
		String dstFP = BASE_DEST_FP + user.getLoginId();

		moveFolder(srcFP, dstFP);
	    }
	} catch (OjiException e) {
	    System.out.println("FAILED");
	    e.printStackTrace();
	}

	return true;
    }

    public boolean CreateUsers() throws OjiException {
	/*
	 * removeUserFromGroups("uA188"); // USER ID - uA188 - avanzyl, Name :Andre van Zyl, objID:
	 * uA188
	 */
	// moveFolder("c:\\test1","C:\\test2");
	// SAR_move_inactivated_users_X_folder();

	createTestUsers(30);
	return true;
    }

    /**
     * Create a new User
     * 
     * classification
     * SPA - INTERNAL INHERITED ==> NULL
     * DSP - EXTERNAL RESTRICTED ==> "External Restricted"
     */
    public boolean createUser(String businessDomain, String name, String email, String lanID, String password)
    throws OjiException {

	boolean result = false;

	final String ActiveUserGroupID = "gA2";
	final String HomeFolderParentID = "fA9";
	final String SPAGroupID = "gA6";
	final String securityClearance_itnernal = "Internal Restricted";
	final String securityClearance_external = "External Restricted";
	final String classification_external = "External Restricted";

	if (!isExistingUser(lanID)) {
	    OjiGroup activeUserGroup = (OjiGroup) apiSession.getObject(ActiveUserGroupID);
	    OjiFolder HomeFolderParent = (OjiFolder) apiSession.getObject(HomeFolderParentID);

	    OjiUser newUser = apiSession.initUser();
	    newUser.setName(name);
	    newUser.setEmailAddress(email);
	    newUser.setLoginId(lanID);
	    newUser.setParent(activeUserGroup);
	    newUser.setHomeFolderParent(HomeFolderParent);
	    newUser.setPassword(password);

	    if (businessDomain.equalsIgnoreCase("SPA")) {
		newUser.setSecurityClearance(securityClearance_itnernal);
		newUser.create();
		OjiGroup SPAGroup = (OjiGroup) apiSession.getObject(SPAGroupID);
		newUser.createAlias(SPAGroup);
	    } else {
		newUser.setSecurityClearance(securityClearance_external);
		newUser.setClassification(classification_external);
		newUser.create();
	    }
	    newUser.update();
	    result = true;
	} else {
	    System.err.println("Failed created a new user: (EXISTING USER)   " + name);
	    result = false;
	}
	return result;
    }

    public boolean group1(String objID) throws OjiException {
	/*
	 * PARENT FOLDER is CHANGED TO INACTIVE SET INACTIVE ATTRIBUTE
	 */

	//com.objective.client.ObjGroup test;
	OjiGroup myGroup = (OjiGroup) apiSession.getObject(objID);

	Set<com.objective.client.ObjGroup> belongGroups;
	belongGroups = myGroup.getBelongingGroups();
	Iterator<com.objective.client.ObjGroup> i1 = belongGroups.iterator();
	while (i1.hasNext()) {
	    com.objective.client.ObjGroup group = (com.objective.client.ObjGroup) i1.next();
	    System.out.println(group.getName());
	}

	System.out.println("-------------");

	Set<OjiGroup> contentGroups = (Set<OjiGroup>) myGroup.getContents();

	Iterator<OjiGroup> i2 = contentGroups.iterator();
	while (i2.hasNext()) {
	    OjiGroup group = (OjiGroup) i2.next();
	    System.out.println(group.getName());
	}
	return true;
    }

    public boolean isExistingUser(String userLanID) {
	boolean result = false;

	int Max_return_count = 10;

	try {

	    Search_Builder newSearch = new Search_Builder(apiSession, Max_return_count);
	    newSearch.set_Search_type("user");
	    newSearch.addCriteria("user signon", "is exactly", userLanID);

	    Collection<OjiObject> searchReturns;
	    searchReturns = newSearch.execute();

	    Iterator<OjiObject> i = searchReturns.iterator();

	    if (i.hasNext()) {
		OjiObject searchResult = i.next();
		OjiUser existUser = (OjiUser) apiSession.getObject(searchResult.getObjId());
		System.err.println("The User Exists - " + existUser.getName().trim());
		result = true;
	    } else
		result = false;

	} catch (OjiException e) {
	    e.printStackTrace();
	}

	return result;

    }

    private int Search_Users_Count(String clearance, String active, String beginDate, String endDate) {

	/*
	 * clearance = SPA / DSP activeStatus = ACTIVE / INACTIVE
	 */
	final int Max_return_count = 3000;
	int user_count = 0;

	try {
	    Search_Builder userSearch = new Search_Builder(apiSession, Max_return_count);
	    userSearch.set_Search_type("user");

	    if (active == "ACTIVE") {
		userSearch.addCriteria("date inactivated", "is blank", "");
		userSearch.addCriteria("date disabled", "is blank", "");
		userSearch.addCriteria("creation date", "is on or after", beginDate);
		userSearch.addCriteria("creation date", "is before", endDate);
	    } else {
		userSearch.addCriteria("date inactivated", "is on or after", beginDate);
		userSearch.addCriteria("date inactivated", "is before", endDate);
	    }

	    if (clearance == "SPA") {
		userSearch.addCriteria("security clearance", "is not", Security_Clearance_DSP);
	    } else {
		userSearch.addCriteria("security clearance", "is", Security_Clearance_DSP);
	    }

	    Collection<OjiObject> results = userSearch.execute();
	    user_count = results.size();

	} catch (OjiException e) {
	    System.out.println("FAILED");
	    e.printStackTrace();
	}

	return user_count;

    }

    public boolean Search_SAR(String beginDATE, String endDATE) {

	// DATE FORMAT "29-1-2006 22:01:01"
	// endDATE = getDateString( beginDATE, (1000*60*60*1));

	String initDATE = "1-1-2005 00:00:01";

	System.out.println("========================");

	int count_Active_SPA_total = Search_Users_Count("SPA", "ACTIVE", initDATE, endDATE);
	int count_Active_DSP_total = Search_Users_Count("DSP", "ACTIVE", initDATE, endDATE);
	int count_Inactive_SPA_total = Search_Users_Count("SPA", "INACTIVE", initDATE, endDATE);
	int count_Inactive_DSP_total = Search_Users_Count("DSP", "INACTIVE", initDATE, endDATE);

	System.out.print(" TOTAL Activated:    ");
	System.out.println(count_Active_SPA_total + "(SPA) " + "+ " + count_Active_DSP_total + "(DSP) " + " = "
		+ (count_Active_DSP_total + count_Active_SPA_total));
	System.out.print(" TOTAL Inactivated:  ");
	System.out.println(count_Inactive_SPA_total + "(SPA) " + "+ " + count_Inactive_DSP_total + "(DSP) " + " = "
		+ (count_Inactive_SPA_total + count_Inactive_DSP_total));

	System.out.println("========================");
	System.out.println("From : " + beginDATE + "   Before :" + endDATE);

	try {
	    System.out.println(" Activated:   " + Search_Users_Count("SPA", "ACTIVE", beginDATE, endDATE) + "(SPA)  "
		    + Search_Users_Count("DSP", "ACTIVE", beginDATE, endDATE) + "(DSP)");
	    System.out.println(" Inactivated: " + Search_Users_Count("SPA", "INACTIVE", beginDATE, endDATE) + "(SPA)  "
		    + Search_Users_Count("DSP", "INACTIVE", beginDATE, endDATE) + "(DSP)");

	} catch (Exception e) {
	    System.out.println("FAILED");
	    e.printStackTrace();
	}
	return true;
    }

    public boolean Search_user_match() {
	// Search_delisted_users("C:\\user_list.txt");
	return true;
    }


    public boolean user_belonged_group() {

	// ***************

	int Max_return_count = 1000;
	Search_Builder newSearch_Alias = new Search_Builder(apiSession, Max_return_count);

	try {
	    newSearch_Alias.set_Search_type("alias");
	    newSearch_Alias.addCriteria("parent group", "is", "gA25");
	} catch (OjiException e) {
	    e.printStackTrace();
	}

	Collection<OjiObject> searchReturns;
	searchReturns = newSearch_Alias.execute();
	Iterator<OjiObject> i = searchReturns.iterator();

	while (i.hasNext()) {
	    OjiObject searchResult = i.next();
	    String alias_name = searchResult.getLabelForView();
	    String user_name = alias_name.replace(" alias", "");
	    System.out.println("SEARCH: " + user_name);
	}

	Search_Builder newSearch = new Search_Builder(apiSession, Max_return_count);
	try {
	    newSearch_Alias.set_Search_type("group");
	    newSearch_Alias.addCriteria("parent group", "is", "gA25");
	} catch (OjiException e) {
	    e.printStackTrace();
	}
	return true;

    }



    public boolean Search_delisted_users_CHANGE(String filepath_delisted_userlist) {
	return Search_delisted_users(filepath_delisted_userlist, "OBJECTIVE");
    }

    public boolean Search_delisted_users_MOVE_X_DRIVE(String filepath_delisted_userlist) {
	return Search_delisted_users(filepath_delisted_userlist, "XMOVE");
    }

    public boolean Search_delisted_users_SEARCH_ONLY(String filepath_delisted_userlist) {
	return Search_delisted_users(filepath_delisted_userlist, "SEARCH");
    }


    private boolean Search_delisted_users(String filepath_delisted_userlist, String APPLY_CHANGE) {

	/*
	 * SEARCH --------------------------- 1.READ USER INPUT FILE from C:\DEV\INPUT 2.BUILD USER
	 * ARRAY 3.SEARCH THE
	 * USER from OBJECTIVE 4.LIST MATCHED USERS on SCREEN
	 */

	List<String> userID_list = new ArrayList<String>();

	try {
	    FileInputStream fstream = new FileInputStream(filepath_delisted_userlist);
	    DataInputStream in = new DataInputStream(fstream);
	    BufferedReader br = new BufferedReader(new InputStreamReader(in));
	    String strLine;
	    while ((strLine = br.readLine()) != null) {
		if (strLine.length() > 10) {
		    userID_list.add(strLine);
		    System.out.println(":Line Added - " + strLine);
		}
	    }
	    in.close();
	} catch (Exception e) {
	    System.err.println("Error: " + e.getMessage());
	    e.printStackTrace();
	}
	System.out.println("\n \n :Search results----------------------- \n");
	Iterator<String> it = userID_list.iterator();
	while (it.hasNext()) {
	    String textLine = it.next();
	    String[] strArray;
	    String userLanID;

	    strArray = textLine.split("\\("); // " id, aneill"
	    strArray = strArray[1].split("\\,");
	    userLanID = strArray[0].trim(); // "aneill"

	    try {
		OjiSearch newSearch = apiSession.initAdvancedSearch();
		OjiTypeDefn search_type = apiSession.getTypeDefnByName("user");
		newSearch.setObjectSearchType(search_type);
		newSearch.addCriteria("user signon", "is exactly", userLanID, 0, 0, OjiSearch.AND_RELATION);
		newSearch.execute();

		Collection<OjiObject> results = newSearch.getResults();
		Iterator<OjiObject> i = results.iterator();

		while (i.hasNext()) {
		    OjiObject searchResult = i.next();
		    System.out.println("Matched User Id : " + userLanID + ", Name :" + searchResult.getLabelForView()
			    + ", objID: " + searchResult.getObjId());

		    if (APPLY_CHANGE == "OBJECTIVE") {
			System.out.println("Inactivate User : " + searchResult.getLabelForView());
			SAR_setUserInactive(searchResult.getObjId());
		    } else if (APPLY_CHANGE == "XMOVE") {
			SAR_move_inactivated_users_X_folder();
		    } else if (APPLY_CHANGE == "SEARCH") {
			// NO ACTION
		    }
		}

	    } catch (OjiException e) {
		System.out.println("QUERY FAILED");
		System.err.println("Error: " + e.getMessage());
		e.printStackTrace();
	    }
	}
	System.out.println(">> Completed processing.");
	return true;
    }

    private boolean moveFolder(String srcFP, String dstFP) throws OjiException {

	File srcFolder = new File(srcFP);
	File dstFolder = new File(dstFP);

	System.out.print(srcFP + " ==>	" + dstFP + "			");

	if (srcFolder.exists()) {
	    if (dstFolder.exists()) {
		System.out.println(">> Failed: Destination Folder does exist");
	    } else {
		boolean success = srcFolder.renameTo(dstFolder);
		// boolean success = srcFolder.renameTo(new File(dstFolder,
		// srcFolder.getName()));
		if (!success)
		    System.out.println(">> Failed: MOVE FOLDER()  ");
		else
		    System.out.println(">> Success: Folder has been moved ");
	    }
	} else
	    System.out.println("SRC folder does not exist");
	return true;

    }



}
